using System;
using System.Collections.Generic;
using System.Text;

namespace Affirma.CloudFront.AdminTool
{
    public class FolderTreeObject
    {
        public string FullKeyName;
        public string ShortKeyName;
        public string Size;
        public string Date;

        public FolderTreeObject(string fullKeyName, string size, string date)
        {
            this.FullKeyName = fullKeyName;
            this.Size = size;
            this.Date = date;

            int index = fullKeyName.LastIndexOf('/');
            if (index > 0)
            {
                this.ShortKeyName = fullKeyName.Substring(index + 1);
            }
            else
            {
                this.ShortKeyName = this.FullKeyName;
            }
        }
    }

    public class FolderTreeNode
    {
        public List<FolderTreeNode> Children;
        public List<FolderTreeObject> S3Objects;
        public string Name;

        public FolderTreeNode(string name)
        {
            this.Children = new List<FolderTreeNode>();
            this.S3Objects = new List<FolderTreeObject>();
            this.Name = name;
        }

        public void AddObject(FolderTreeObject o)
        {
            Queue<string> folders = new Queue<string>();

            if (!o.FullKeyName.Contains("/"))
            {
                this.S3Objects.Add(o);
                return;
            }

            string[] bites = o.FullKeyName.Split('/');

            for (int i = 0; i < bites.Length - 1; i++)
            {
                folders.Enqueue(bites[i]);
            }

            AddObject(o, folders);

        }

        public void AddObject(FolderTreeObject o, Queue<string> folders)
        {
            if (folders.Count == 0)
            {
                this.S3Objects.Add(o);
                return;
            }

            string nextFolderName = folders.Dequeue();
            FolderTreeNode nextFolderChild = this.GetChildByName(nextFolderName);

            if (nextFolderChild == null)
            {
                nextFolderChild = new FolderTreeNode(nextFolderName);
                this.Children.Add(nextFolderChild);
            }

            nextFolderChild.AddObject(o, folders);
        }

        private FolderTreeNode GetChildByName(string name)
        {
            foreach (FolderTreeNode child in this.Children)
            {
                if (child.Name == name)
                {
                    return child;
                }
            }

            return null;
        }

        public FolderTreeObject[] GetObjects(string foldername)
        {
            Queue<string> folders = new Queue<string>();

            string fName = foldername;
            if (fName.StartsWith("/"))
            {
                fName = fName.Substring(1);
            }
            if (fName.EndsWith("/"))
            {
                fName = fName.Substring(0, fName.Length - 1);
            }

            string[] tokens = fName.Split('/');
            if (foldername == "/")
            {
                return this.S3Objects.ToArray();
            }

            for (int i = 0; i < tokens.Length; i++)
            {
                folders.Enqueue(tokens[i]);
            }

            return GetObjects(folders);
        }

        public FolderTreeObject[] GetObjects(Queue<string> folders)
        {
            if (folders.Count == 0)
            {
                return this.S3Objects.ToArray();
            }

            string nextFolderName = folders.Dequeue();

            FolderTreeNode nextFolderChild = this.GetChildByName(nextFolderName);

            if (nextFolderChild == null)
            {
                return new FolderTreeObject[0];
            }

            return nextFolderChild.GetObjects(folders);
        }
    }
}
